package br.ufrj.ppgi.jemf_advanced_example.plan;

import android.app.Activity;
import android.database.Cursor;
import android.graphics.Color;
import android.os.Bundle;
import android.app.ListFragment;
import android.app.LoaderManager.LoaderCallbacks;
import android.widget.CursorAdapter;
import android.util.Log;
import android.view.Gravity;
import android.view.View;
import android.widget.AbsListView;
import android.widget.AdapterView;
import android.widget.LinearLayout;
import android.widget.ListView;
import android.widget.TextView;
import br.ufrj.ppgi.jemf.mobile.FeatureHolder.EnumFeatureType;
import br.ufrj.ppgi.jemf.mobile.bean.Plan;
import br.ufrj.ppgi.jemf.mobile.factory.EmergencyManagementFactory;
import br.ufrj.ppgi.jemf_advanced_example.CustomActionListener;
import br.ufrj.ppgi.jemf_advanced_example.CustomSwipeDismissListener;
import br.ufrj.ppgi.jemf_advanced_example.CustomActionListener.BaseActionListener;
import br.ufrj.ppgi.jemf_advanced_example.CustomSwipeDismissListener.OnSwipeDismissListener;
import br.ufrj.ppgi.jemf_advanced_example.BuildConfig;

/**
 * A list fragment representing a list of Emergencies.
 * This fragment also supports tablet devices by allowing list items to be given an 'activated' state upon selection.
 * This helps indicate which item is currently being viewed in a {@link PlanDetailFragment}.
 * <p>
 * Activities containing this fragment MUST implement the {@link Callbacks} interface.
 */
public class PlanListFragment extends ListFragment implements OnSwipeDismissListener {

	// JEMF instance
    private EmergencyManagementFactory emf = null;
    // Cursor Adapter
    private CursorAdapter adapter = null;
    // Loader
    private LoaderCallbacks<Cursor> loaderCall = null;
    // Loader ID
	private final int loaderID = 1;
	// Swipe Listener
	private CustomSwipeDismissListener touchListener = null;



    /**
     * The serialization (saved instance state) Bundle key representing the activated item position.
     * Only used on tablets.
     */
    private static final String STATE_ACTIVATED_POSITION = "activated_position";
    /**
     * The current activated item position. Only used on tablets.
     */
    private int mActivatedPosition = ListView.INVALID_POSITION;



    /**
     * The fragment's current callback object, which is notified of list item clicks.
     */
    private BaseActionListener actionListener = dummyActions;
    /**
     * A implementation of the {@link CustomActionListener} interface that does nothing.
     * Used only when this fragment is not attached to an activity.
     */
    private static BaseActionListener dummyActions = new BaseActionListener() {
		@Override
		public <T> void onItemSelected(T bean) {
		}
		@Override
		public <T> T onItemSave(T bean) {
			return bean;
		}
		@Override
		public <T> void onItemRemove(T bean) {
		}
	};





    /**
     * Mandatory empty constructor for the fragment manager to instantiate the fragment (e.g. upon screen orientation changes).
     */
    public PlanListFragment() {
    }

    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);


        // JEMF
        this.emf = EmergencyManagementFactory.newInstance(getActivity());
        // Adapter
		this.adapter = this.emf.getMainFactory(EnumFeatureType.PLAN).getAdapter();
		setListAdapter(adapter);
		// Load the content
		this.loaderCall = this.emf.getMainFactory(EnumFeatureType.PLAN).getLoader(null, null, null);
		// Prepare the loader. Either re-connect with an existing one, or start a new one.
		if (getActivity().getLoaderManager().getLoader(loaderID) != null && !getActivity().getLoaderManager().getLoader(this.loaderID).isReset()) {
			getLoaderManager().restartLoader(this.loaderID, null, this.loaderCall);
		} else {
			getLoaderManager().initLoader(this.loaderID, null, this.loaderCall);
		}
    }

    @Override
    public void onViewCreated(View view, Bundle savedInstanceState) {
        super.onViewCreated(view, savedInstanceState);
        // Restore the previously serialized activated item position.
        if (savedInstanceState != null) {
        	if (savedInstanceState.containsKey(STATE_ACTIVATED_POSITION)) {
                setActivatedPosition(savedInstanceState.getInt(STATE_ACTIVATED_POSITION));
        	}
        }

		// SwipeToDismiss
        this.touchListener = new CustomSwipeDismissListener(getListView(), this);
        getListView().setOnTouchListener(this.touchListener);

        // Layout changes
        int whiteColor = Color.rgb(255, 255, 255);
        int grayColor = Color.rgb(200, 200, 200);
        TextView empty = new TextView(getActivity());
        empty.setText("No data to display.");
        empty.setTextSize(14);
        empty.setTextColor(grayColor);
        empty.setBackgroundColor(whiteColor);
        empty.setLayoutParams(new LinearLayout.LayoutParams(android.view.ViewGroup.LayoutParams.MATCH_PARENT, android.view.ViewGroup.LayoutParams.MATCH_PARENT));
        empty.setGravity(Gravity.CENTER);
        getActivity().addContentView(empty, new LinearLayout.LayoutParams(android.view.ViewGroup.LayoutParams.MATCH_PARENT, android.view.ViewGroup.LayoutParams.MATCH_PARENT));
        // Setting background view
        getListView().setEmptyView(empty);
        getListView().setBackgroundColor(whiteColor);
    }
    @Override
    public void onAttach(Activity activity) {
        super.onAttach(activity);
        // Activities containing this fragment must implement its ActionListener callbacks.
        if (!(activity instanceof BaseActionListener)) {
            throw new IllegalStateException("Activity must implement fragment's ActionListener callbacks.");
        }
        actionListener = (BaseActionListener) activity;
    }
    @Override
    public void onDetach() {
        super.onDetach();
        // Reset the active ActionListener callbacks interface to the dummy implementation.
        actionListener = dummyActions;
    }



    @Override
    public void onSaveInstanceState(Bundle outState) {
        super.onSaveInstanceState(outState);
        if (mActivatedPosition != AdapterView.INVALID_POSITION) {
            // Serialize and persist the activated item position.
            outState.putInt(STATE_ACTIVATED_POSITION, mActivatedPosition);
        }
    }
    /**
     * Turns on activate-on-click mode. When this mode is on, list items will be given the 'activated' state when touched.
     */
    public void setActivateOnItemClick(boolean activateOnItemClick) {
        // When setting CHOICE_MODE_SINGLE, ListView will automatically give items the 'activated' state when touched.
        getListView().setChoiceMode(activateOnItemClick ? AbsListView.CHOICE_MODE_SINGLE : AbsListView.CHOICE_MODE_NONE);
    }
    private void setActivatedPosition(int position) {
        if (position == AdapterView.INVALID_POSITION) {
            getListView().setItemChecked(mActivatedPosition, false);
        } else {
            getListView().setItemChecked(position, true);
        }
        mActivatedPosition = position;
    }



    /**
     * Get the selected item
     * @param position
     * @return Plan
     */
    private Plan getSelectedPlan(int position) {
    	Plan result = null;
	    Cursor cursor = (Cursor) getListAdapter().getItem(position);
	    if (cursor != null) {
	        result = this.emf.getMainFactory(EnumFeatureType.PLAN).getManager().deserialize(cursor);
	        if (result != null) {
	        	if (BuildConfig.DEBUG) Log.i(PlanListActivity.TAG, "PlanListFragment ::: getSelectedPlan"/* + result.toString()*/);
	        }
	    }
    	return result;
    }
    @Override
    public void onListItemClick(ListView listView, View view, int position, long id) {
		    super.onListItemClick(listView, view, position, id);		    
		    // Notify the active callbacks interface (the activity, if the fragment is attached to one) that an item has been selected.
		    actionListener.onItemSelected(getSelectedPlan(position));
    }



    /**
     * Verify if list item is dismissable.
     * In this case, if Plan is not activated
     */
    @Override
	public boolean isSwipeDismissable(int position) {
    	if (BuildConfig.DEBUG) Log.i(PlanListActivity.TAG, "PlanListFragment ::: isSwipeDismissable");
    	Plan Plan = getSelectedPlan(position);
        if (Plan != null) {
    		return true;
        }
        return false;
	}
    /**
     * Execute action swipe to dismiss
     */
	@Override
	public void onSwipeDismiss(ListView listView, View view, int position) {
		if (BuildConfig.DEBUG) Log.i(PlanListActivity.TAG, "PlanListFragment ::: onSwipeDismiss");
		final View currentView = view;
		// Get selected item
		Plan plan = getSelectedPlan(position);
        if (plan != null) {
           	// Delete Plan
        	actionListener.onItemRemove(plan);
    		// Refresh ListView
            CustomSwipeDismissListener.resetAnimation(currentView);
            currentView.requestLayout();
        }
	}
}
